import 'package:flutter/cupertino.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter_pagewise/flutter_pagewise.dart';
import 'package:loxen/api/api.dart';
import 'package:loxen/api/http_server/dictionaries.dart';
import 'package:loxen/api/http_server/like.dart';
import 'package:loxen/mode/base_mode.dart';
import 'package:loxen/mode/inspiration/catgory_list.dart';
import 'package:loxen/mode/inspiration/inspiration_info_bean.dart';
import 'package:loxen/mode/inspiration/inspiration_page.dart';
import 'package:loxen/mode/inspiration/inspiration_style_bean.dart';
import 'package:loxen/mode/like_bean.dart';
import 'package:loxen/viewmode/base_view_model.dart';
import 'package:rxdart/rxdart.dart';

class InspirationListViewModel extends BaseViewModel with LikeMixin {
  BaseMode<CategoryList> _categoryBean;

  BaseMode<CategoryList> get categoryBean => _categoryBean;

  InspirationStyleBean _styleBean;

  InspirationStyleBean get styleBean => _styleBean;
  Style _style;

  Style get style => _style;

  int currentCategory = 0;
  int currentCategoryId = 0;

  Map<String, List<List<InspirationInfo>>> _map = {};


  PagewiseLoadController pageController;

  InspirationListViewModel(){
    pageController = PagewiseLoadController<InspirationInfo>(
        pageFuture:nextData,
        pageSize: 5);
  }

  void unCollection(InspirationInfo entity) {
    ApiService.unCollection(ContentType.IDEA_ARTICLE, entity.id.toString()).listen((event) {
      if (event.statusCode == 200) {
        entity.is_collect = 0;
        entity.collect_num -= 1;
        notifyListeners();
      }
    }, onError: (error, stack) {
      print(error);
      print(stack);
    });
  }

  //点赞
  void likeArticle(InspirationInfo entity) {
    if (entity != null) {
      if (entity.is_like == 0) {
        like(ContentType.IDEA_ARTICLE, entity.id.toString()).listen((event) {
          if (event != null) {
            entity.is_like = 1;
            entity.like_num = event.like_num;
            notifyListeners();
          }
        }, onError: (error, stack) {
          print(stack);
          print(error);
        });
      } else {
        unLike(ContentType.IDEA_ARTICLE, entity.id.toString()).listen((event) {
          if (event != null) {
            entity.is_like = 0;
            entity.like_num = event.like_num;
            notifyListeners();
          }
        }, onError: (error) => print(error));
      }
    }
  }

  //风格修改
  void changeStyle(Style style) {
    _style = style;
    _map.clear();
    pageController.reset();
    notifyListeners();
  }

  //内容修改
  void changeEntity() {
    notifyListeners();
  }

  //刷新列表内容
  void refresh() {
    String key = _categoryBean.data.results[currentCategory].sub_category[currentCategoryId].id;
    if(_map.containsKey(key)) {
      _map[key].clear();
    }
    pageController.reset();
  }

  //一级分类切换
  void changeCategory(int index) {
    currentCategory = index;
    changeCategoryId(0);
    notifyListeners();
  }

  //二级分类切换
  void changeCategoryId(int index) {
    currentCategoryId = index;
    pageController.reset();
    notifyListeners();
  }

  //下一页数据
  Future<List<InspirationInfo>> nextData(int page) async {
    String key = _categoryBean.data.results[currentCategory].sub_category[currentCategoryId].id;
    if (_map.containsKey(key)) {
      if (_map[key].length - 1 >= page) {
        return _map[key][page];
      } else {
        var data = await ApiService.interceptListData(key, page + 1, style: _style?.id)
            .flatMap((value) => compute(decodeInspirationBean, value.data).asStream())
            .first;
        _map[key].add(data.data.results);
        return data.data.results;
      }
    } else {
      var data = await ApiService.interceptListData(key, page + 1, style: _style?.id)
          .flatMap((value) => compute(decodeInspirationBean, value.data).asStream())
          .first;
      _map.putIfAbsent(key, () => <List<InspirationInfo>>[data.data.results]);
      return data.data.results;
    }
  }

  //加载数据
  void loadData() {
    Rx.zip2<BaseMode<CategoryList>, InspirationStyleBean, String>(_getCategoryBean(), _getStyle(),
            (category, style) {
      if (category.code == 2000) {
        _styleBean = style;
        _categoryBean = category;
        String key = category.data.results[currentCategory].sub_category[currentCategoryId].id;
        return key;
      }
      throw "类型请求失败！";
    })
        .doOnListen(() {
          _map.clear();
          mState = BaseState.LOADING;
          notifyListeners();
        })
        .flatMap((key) => _getInspirationBean(key))
        .listen((event) {
          if (event.data != null) {
            mState = BaseState.CONTENT;
            String key =
                _categoryBean.data.results[currentCategory].sub_category[currentCategoryId].id;
            _map.putIfAbsent(key, () => <List<InspirationInfo>>[event.data.results]);
          } else {
            mState = BaseState.EMPTY;
          }
        }, onError: (error, stackTrace) {
          print(error);
          print(stackTrace);
          mState = BaseState.FAIL;
        }, onDone: () => notifyListeners());
  }

  Stream<BaseMode<InspirationPage>> _getInspirationBean(String key) {
    return ApiService.interceptListData(key, 1, style: _style?.id)
        .flatMap((value) => compute(decodeInspirationBean, value.data).asStream());
  }

  Stream<InspirationStyleBean> _getStyle() {
    return ApiService.inspirationStyle()
        .flatMap((value) => compute(decodeStyleBean, value.data).asStream());
  }

  Stream<BaseMode<CategoryList>> _getCategoryBean() {
    return ApiService.inspirationCategory()
        .flatMap((value) => compute(decodeCategoryBean, value.data).asStream());
  }

  static InspirationStyleBean decodeStyleBean(dynamic json) {
    return InspirationStyleBean.fromJson(json);
  }

  static LikeBean decodeLikeBean(dynamic json) {
    return LikeBean.fromJson(json);
  }

  static BaseMode<InspirationPage> decodeInspirationBean(dynamic json) {
    return BaseMode<InspirationPage>(json);
  }

  static BaseMode<CategoryList> decodeCategoryBean(dynamic json) {
    return BaseMode<CategoryList>(json);
  }
}
